added samples
[windows-sources.git] / sdk / samples / all in on code / Visual Studio 2008 / VBFTPDownload / FTPFileSystem.vb
blob71e3d8d70d065a3ef8f02d0716dc377e63bae5ea
1 '*************************** Module Header ******************************'
2 ' Module Name: FTPFileSystem.vb
3 ' Project: VBFTPDownload
4 ' Copyright (c) Microsoft Corporation.
5 '
6 ' The class FTPFileSystem represents a file on the remote FTP server. When run
7 ' the FTP LIST protocol method to get a detailed listing of the files on an
8 ' FTP server, the server will response many records of information. Each record
9 ' represents a file. Depended on the FTP Directory Listing Style of the server,
10 ' the record is like
11 ' 1. MSDOS
12 ' 1.1. Directory
13 ' 12-13-10 12:41PM <DIR> Folder A
14 ' 1.2. File
15 ' 12-13-10 12:41PM [Size] File B
17 ' NOTE: The date segment is like "12-13-10" instead of "12-13-2010" if Four-digit
18 ' years is not checked in IIS.
20 ' 2. UNIX
21 ' 2.1. Directory
22 ' drwxrwxrwx 1 owner group 0 Dec 1 12:00 Folder A
23 ' 2.2. File
24 ' -rwxrwxrwx 1 owner group [Size] Dec 1 12:00 File B
26 ' NOTE: The date segment does not contains year.
29 ' This source is subject to the Microsoft Public License.
30 ' See http://www.microsoft.com/opensource/licenses.mspx#Ms-PL.
31 ' All other rights reserved.
33 ' THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
34 ' EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED
35 ' WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
36 '*************************************************************************'
38 Imports System.Text.RegularExpressions
39 Imports System.Text
41 Public Class FTPFileSystem
43 Dim _originalRecordString As String
45 ''' <summary>
46 ''' The original record string.
47 ''' </summary>
48 Public Property OriginalRecordString() As String
49 Get
50 Return _originalRecordString
51 End Get
52 Set(ByVal value As String)
53 _originalRecordString = value
54 End Set
55 End Property
57 Dim _directoryListingStyle As FTPDirectoryListingStyle
59 ''' <summary>
60 ''' MSDOS or UNIX.
61 ''' </summary>
62 Public Property DirectoryListingStyle() As FTPDirectoryListingStyle
63 Get
64 Return _directoryListingStyle
65 End Get
66 Set(ByVal value As FTPDirectoryListingStyle)
67 _directoryListingStyle = value
68 End Set
69 End Property
71 Dim _url As Uri
73 ''' <summary>
74 ''' The server Path.
75 ''' </summary>
76 Public Property Url() As Uri
77 Get
78 Return _url
79 End Get
80 Set(ByVal value As Uri)
81 _url = value
82 End Set
83 End Property
85 Dim _name As String
87 ''' <summary>
88 ''' The name of this FTPFileSystem instance.
89 ''' </summary>
90 Public Property Name() As String
91 Get
92 Return _name
93 End Get
94 Set(ByVal value As String)
95 _name = value
96 End Set
97 End Property
99 Dim _isDirectory As Boolean
101 ''' <summary>
102 ''' Specify whether this FTPFileSystem instance is a directory.
103 ''' </summary>
104 Public Property IsDirectory() As Boolean
106 Return _isDirectory
107 End Get
108 Set(ByVal value As Boolean)
109 _isDirectory = value
110 End Set
111 End Property
113 Dim _modifiedTime As Date
115 ''' <summary>
116 ''' The last modified time of this FTPFileSystem instance.
117 ''' </summary>
118 Public Property ModifiedTime() As Date
120 Return _modifiedTime
121 End Get
122 Set(ByVal value As Date)
123 _modifiedTime = value
124 End Set
125 End Property
127 Dim _size As Integer
129 ''' <summary>
130 ''' The size of this FTPFileSystem instance if it is not a directory.
131 ''' </summary>
132 Public Property Size() As Integer
134 Return _size
135 End Get
136 Set(ByVal value As Integer)
137 _size = value
138 End Set
139 End Property
141 Private Sub New()
142 End Sub
144 ''' <summary>
145 ''' Override the method ToString() to display a more friendly message.
146 ''' </summary>
147 Public Overrides Function ToString() As String
148 Return String.Format("{0}" & vbTab & "{1}" & vbTab & vbTab & "{2}", _
149 Me.ModifiedTime.ToString("yyyy-MM-dd HH:mm"), _
150 If(Me.IsDirectory, "<DIR>", Me.Size.ToString()), Me.Name)
151 End Function
153 ''' <summary>
154 ''' Find out the FTP Directory Listing Style from the recordString.
155 ''' </summary>
156 Public Shared Function GetDirectoryListingStyle(ByVal recordString As String) _
157 As FTPDirectoryListingStyle
158 Dim regex_Renamed As Regex = _
159 New System.Text.RegularExpressions.Regex("^[d-]([r-][w-][x-]){3}$")
161 Dim header As String = recordString.Substring(0, 10)
163 ' If the style is UNIX, then the header is like "drwxrwxrwx".
164 If regex_Renamed.IsMatch(header) Then
165 Return FTPDirectoryListingStyle.UNIX
166 Else
167 Return FTPDirectoryListingStyle.MSDOS
168 End If
169 End Function
171 ''' <summary>
172 ''' Get an FTPFileSystem from the recordString.
173 ''' </summary>
174 Public Shared Function ParseRecordString(ByVal baseUrl As Uri, _
175 ByVal recordString As String, _
176 ByVal type As FTPDirectoryListingStyle) _
177 As FTPFileSystem
178 Dim fileSystem As FTPFileSystem = Nothing
180 If type = FTPDirectoryListingStyle.UNIX Then
181 fileSystem = ParseUNIXRecordString(recordString)
182 Else
183 fileSystem = ParseMSDOSRecordString(recordString)
184 End If
186 ' Add "/" to the url if it is a directory
187 fileSystem.Url = New Uri(baseUrl, fileSystem.Name _
188 & (If(fileSystem.IsDirectory, "/", String.Empty)))
190 Return fileSystem
191 End Function
193 ''' <summary>
194 ''' The recordString is like
195 ''' Directory: drwxrwxrwx 1 owner group 0 Dec 13 11:25 Folder A
196 ''' File: -rwxrwxrwx 1 owner group 1024 Dec 13 11:25 File B
197 ''' NOTE: The date segment does not contains year.
198 ''' </summary>
199 Shared Function ParseUNIXRecordString(ByVal recordString As String) As FTPFileSystem
200 Dim fileSystem As New FTPFileSystem()
202 fileSystem.OriginalRecordString = recordString.Trim()
203 fileSystem.DirectoryListingStyle = FTPDirectoryListingStyle.UNIX
205 ' The segments is like "drwxrwxrwx", "", "", "1", "owner", "", "", "",
206 ' "group", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "",
207 ' "0", "Dec", "13", "11:25", "Folder", "A".
208 Dim segments() As String = fileSystem.OriginalRecordString.Split(" "c)
210 Dim index As Integer = 0
212 ' The permission segment is like "drwxrwxrwx".
213 Dim permissionsegment As String = segments(index)
215 ' If the property start with 'd', then it means a directory.
216 fileSystem.IsDirectory = permissionsegment.Chars(0) = "d"c
218 ' Skip the empty segments.
219 index += 1
220 Do While segments(index) = String.Empty
221 index += 1
222 Loop
224 ' Skip the directories segment.
226 ' Skip the empty segments.
227 index += 1
228 Do While segments(index) = String.Empty
229 index += 1
230 Loop
232 ' Skip the owner segment.
234 ' Skip the empty segments.
235 index += 1
236 Do While segments(index) = String.Empty
237 index += 1
238 Loop
240 ' Skip the group segment.
242 ' Skip the empty segments.
243 index += 1
244 Do While segments(index) = String.Empty
245 index += 1
246 Loop
248 ' If this fileSystem is a file, then the size is larger than 0.
249 fileSystem.Size = Integer.Parse(segments(index))
251 ' Skip the empty segments.
252 index += 1
253 Do While segments(index) = String.Empty
254 index += 1
255 Loop
257 ' The month segment.
258 Dim monthsegment As String = segments(index)
260 ' Skip the empty segments.
261 index += 1
262 Do While segments(index) = String.Empty
263 index += 1
264 Loop
266 ' The day segment.
267 Dim daysegment As String = segments(index)
269 ' Skip the empty segments.
270 index += 1
271 Do While segments(index) = String.Empty
272 index += 1
273 Loop
275 ' The time segment.
276 Dim timesegment As String = segments(index)
278 fileSystem.ModifiedTime = _
279 Date.Parse(String.Format("{0} {1} {2} ", _
280 timesegment, monthsegment, daysegment))
282 ' Skip the empty segments.
283 index += 1
284 Do While segments(index) = String.Empty
285 index += 1
286 Loop
288 ' Calculate the index of the file name part in the original string.
289 Dim filenameIndex As Integer = 0
291 For i As Integer = 0 To index - 1
292 ' "" represents ' ' in the original string.
293 If segments(i) = String.Empty Then
294 filenameIndex += 1
295 Else
296 filenameIndex += segments(i).Length + 1
297 End If
298 Next i
299 ' The file name may include many segments because the name can contain ' '.
300 fileSystem.Name = fileSystem.OriginalRecordString.Substring(filenameIndex).Trim()
302 Return fileSystem
303 End Function
305 ''' <summary>
306 ''' 12-13-10 12:41PM <DIR> Folder A
307 ''' </summary>
308 ''' <param name="recordString"></param>
309 ''' <returns></returns>
310 Shared Function ParseMSDOSRecordString(ByVal recordString As String) _
311 As FTPFileSystem
312 Dim fileSystem As New FTPFileSystem()
314 fileSystem.OriginalRecordString = recordString.Trim()
315 fileSystem.DirectoryListingStyle = FTPDirectoryListingStyle.MSDOS
317 ' The segments is like "12-13-10", "", "12:41PM", "", "","", "",
318 ' "", "", "<DIR>", "", "", "", "", "", "", "", "", "", "Folder", "A".
319 Dim segments() As String = fileSystem.OriginalRecordString.Split(" "c)
321 Dim index As Integer = 0
323 ' The date segment is like "12-13-10" instead of "12-13-2010" if Four-digit years
324 ' is not checked in IIS.
325 Dim dateSegment As String = segments(index)
326 Dim dateSegments() As String = _
327 dateSegment.Split(New Char() {"-"c}, StringSplitOptions.RemoveEmptyEntries)
329 Dim month As Integer = Integer.Parse(dateSegments(0))
330 Dim day As Integer = Integer.Parse(dateSegments(1))
331 Dim year As Integer = Integer.Parse(dateSegments(2))
333 ' If year >=50 and year <100, then it means the year 19**
334 If year >= 50 AndAlso year < 100 Then
335 year += 1900
337 ' If year <50, then it means the year 20**
338 ElseIf year < 50 Then
339 year += 2000
340 End If
342 ' Skip the empty segments.
343 index += 1
344 Do While segments(index) = String.Empty
345 index += 1
346 Loop
348 ' The time segment.
349 Dim timesegment As String = segments(index)
351 fileSystem.ModifiedTime = _
352 Date.Parse(String.Format("{0}-{1}-{2} {3}", year, month, day, timesegment))
354 ' Skip the empty segments.
355 index += 1
356 Do While segments(index) = String.Empty
357 index += 1
358 Loop
360 ' The size or directory segment.
361 ' If this segment is "<DIR>", then it means a directory, else it means the
362 ' file size.
363 Dim sizeOrDirSegment As String = segments(index)
365 fileSystem.IsDirectory = _
366 sizeOrDirSegment.Equals("<DIR>", StringComparison.OrdinalIgnoreCase)
368 ' If this fileSystem is a file, then the size is larger than 0.
369 If Not fileSystem.IsDirectory Then
370 fileSystem.Size = Integer.Parse(sizeOrDirSegment)
371 End If
373 ' Skip the empty segments.
374 index += 1
375 Do While segments(index) = String.Empty
376 index += 1
377 Loop
379 ' Calculate the index of the file name part in the original string.
380 Dim filenameIndex As Integer = 0
382 For i As Integer = 0 To index - 1
383 ' "" represents ' ' in the original string.
384 If segments(i) = String.Empty Then
385 filenameIndex += 1
386 Else
387 filenameIndex += segments(i).Length + 1
388 End If
389 Next i
390 ' The file name may include many segments because the name can contain ' '.
391 fileSystem.Name = fileSystem.OriginalRecordString.Substring(filenameIndex).Trim()
393 Return fileSystem
394 End Function
395 End Class